struct Color(u32, u32, u32); //元组
#[test]
pub fn test_area() {
    let wid = 20;
    let len = 30;
    let dim = (wid, len);
    println!("{}", calculate_area(wid, len));
    println!("{}", cal_area(dim));
}

pub fn calculate_area(width: u32, length: u32) -> u32 {
    //width. length没有直接关联，不相干
    width * length
}

pub fn cal_area(dim: (u32, u32)) -> u32 {
    // 紧合起来
    dim.0 * dim.1
}
struct Rectangle {
    width: u32,
    length: u32,
}
impl Rectangle {
    //impl代码块
    pub fn cal_area(&self) -> u32 {
        // 这里使用self也可以：Rust会自动引用或者解引用
        //self相当于上下文。相当于这个fn有上下文，是一个方法。
        self.width * self.length
    }
}
#[test]
pub fn test_auto_refer_auto_dereference() {
    let rect = Rectangle {
        width: 20,
        length: 30,
    };
    println!("area in method: {}", &rect.cal_area()); //这几种调用方法的形式都可以。
    println!("area in method: {}", rect.cal_area()); //原因：Rust会自动引用&&自动解引用。调用方法是会发生这种行为
    println!("area in method: {}", *&rect.cal_area());
}
#[derive(Debug)]
enum IPS {
    IPV4,
    IPV6,
}
//一个地址需要两个组合起来进行表达
struct IPAddr {
    ip_type: IPS,
    addr: String,
}
//Rust简化了这种。引入了enum变体
enum IPs {
    IPV4(u32, u32, u32, u32), //enum变体。涵盖了类型和里面具体的值！！
    IPV6(String),             //我们可以在枚举的变体中，嵌入任何类型的数据！！也可以不关联任何类型。
    IPV8,                     //不关联任何类型，
}

#[test]
pub fn test_ip_enum() {
    let v4 = IPS::IPV4;
    let v6 = IPS::IPV6;
    select_ip_type(v4);
    select_ip_type(v6);
    // select_ip_type(v4); //moved
    select_ip_type(IPS::IPV6); //
    select_ip_type(IPS::IPV6); //为什么没有移动所有权？
    select_ip_type(IPS::IPV4); //
}

fn select_ip_type(ip_type: IPS) {
    println!("{:?}", ip_type)
}
